/*
 * TextRankResumeView.java
 */
package com.sira.textrankresume.gui;

import com.sira.textrankresume.Filtro;
import com.sira.textrankresume.Grafo;
import com.sira.textrankresume.IFiltro;
import com.sira.textrankresume.ITextRankResume;
import com.sira.textrankresume.Sentencia;
import com.sira.textrankresume.TextRankResume;
import java.awt.Color;
import java.io.FileNotFoundException;
import java.io.IOException;
import java.util.logging.Level;
import java.util.logging.Logger;
import org.jdesktop.application.Action;
import org.jdesktop.application.ResourceMap;
import org.jdesktop.application.SingleFrameApplication;
import org.jdesktop.application.FrameView;
import org.jdesktop.application.TaskMonitor;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.io.BufferedReader;
import java.io.FileReader;
import java.util.ArrayList;
import java.util.Iterator;
import java.util.LinkedList;
import java.util.List;
import javax.swing.Timer;
import javax.swing.Icon;
import javax.swing.JDialog;
import javax.swing.JFileChooser;
import javax.swing.JFrame;
import javax.swing.JOptionPane;
import javax.swing.JTable;
import javax.swing.table.DefaultTableModel;
import javax.swing.text.SimpleAttributeSet;
import javax.swing.text.StyleConstants;
import org.jdesktop.application.Application;
import org.jdesktop.application.Task;

/**
 * The application's main frame.
 */
public class TextRankResumeView extends FrameView {

    public TextRankResumeView(SingleFrameApplication app) {
        super(app);

        initComponents();

        // status bar initialization - message timeout, idle icon and busy animation, etc
        ResourceMap resourceMap = getResourceMap();
        int messageTimeout = resourceMap.getInteger("StatusBar.messageTimeout");
        messageTimer = new Timer(messageTimeout, new ActionListener() {

            public void actionPerformed(ActionEvent e) {
                statusMessageLabel.setText("");
            }
        });
        messageTimer.setRepeats(false);
        int busyAnimationRate = resourceMap.getInteger("StatusBar.busyAnimationRate");
        for (int i = 0; i < busyIcons.length; i++) {
            busyIcons[i] = resourceMap.getIcon("StatusBar.busyIcons[" + i + "]");
        }
        busyIconTimer = new Timer(busyAnimationRate, new ActionListener() {

            public void actionPerformed(ActionEvent e) {
                busyIconIndex = (busyIconIndex + 1) % busyIcons.length;
                statusAnimationLabel.setIcon(busyIcons[busyIconIndex]);
            }
        });
        idleIcon = resourceMap.getIcon("StatusBar.idleIcon");
        statusAnimationLabel.setIcon(idleIcon);
        progressBar.setVisible(false);

        // connecting action tasks to status bar via TaskMonitor
        TaskMonitor taskMonitor = new TaskMonitor(getApplication().getContext());
        taskMonitor.addPropertyChangeListener(new java.beans.PropertyChangeListener() {

            public void propertyChange(java.beans.PropertyChangeEvent evt) {
                String propertyName = evt.getPropertyName();
                if ("started".equals(propertyName)) {
                    if (!busyIconTimer.isRunning()) {
                        statusAnimationLabel.setIcon(busyIcons[0]);
                        busyIconIndex = 0;
                        busyIconTimer.start();
                    }
                    progressBar.setVisible(true);
                    progressBar.setIndeterminate(true);
                } else if ("done".equals(propertyName)) {
                    busyIconTimer.stop();
                    statusAnimationLabel.setIcon(idleIcon);
                    progressBar.setVisible(false);
                    progressBar.setValue(0);
                } else if ("message".equals(propertyName)) {
                    String text = (String) (evt.getNewValue());
                    statusMessageLabel.setText((text == null) ? "" : text);
                    messageTimer.restart();
                } else if ("progress".equals(propertyName)) {
                    int value = (Integer) (evt.getNewValue());
                    progressBar.setVisible(true);
                    progressBar.setIndeterminate(false);
                    progressBar.setValue(value);
                }
            }
        });


        estiloPorDefecto = new SimpleAttributeSet();
        estiloResaltado = new SimpleAttributeSet();
        StyleConstants.setBold(estiloResaltado, true);
        StyleConstants.setForeground(estiloResaltado, new Color(175, 175, 175));
    }

    @Action
    public void showAboutBox() {
        if (aboutBox == null) {
            JFrame mainFrame = TextRankResumeApp.getApplication().getMainFrame();
            aboutBox = new TextRankResumeAboutBox(mainFrame);
            aboutBox.setLocationRelativeTo(mainFrame);
        }
        TextRankResumeApp.getApplication().show(aboutBox);
    }

    /** This method is called from within the constructor to
     * initialize the form.
     * WARNING: Do NOT modify this code. The content of this method is
     * always regenerated by the Form Editor.
     */
    @SuppressWarnings("unchecked")
    // <editor-fold defaultstate="collapsed" desc="Generated Code">//GEN-BEGIN:initComponents
    private void initComponents() {

        mainPanel = new javax.swing.JPanel();
        tpPanelP = new javax.swing.JTabbedPane();
        pTexto = new javax.swing.JPanel();
        jLabel1 = new javax.swing.JLabel();
        btImportar = new javax.swing.JButton();
        cbResaltarPalabFiltr = new javax.swing.JCheckBox();
        jScrollPane1 = new javax.swing.JScrollPane();
        tpTexto = new javax.swing.JTextPane();
        pFiltros = new javax.swing.JPanel();
        jLabel5 = new javax.swing.JLabel();
        jScrollPane3 = new javax.swing.JScrollPane();
        tableFiltros = new javax.swing.JTable();
        btImportarF = new javax.swing.JButton();
        pResultado = new javax.swing.JPanel();
        jLabel2 = new javax.swing.JLabel();
        jScrollPane2 = new javax.swing.JScrollPane();
        tableResultados = new javax.swing.JTable();
        btMostrar = new javax.swing.JButton();
        btTratar = new javax.swing.JButton();
        jLabel3 = new javax.swing.JLabel();
        cbFiltro = new javax.swing.JCheckBox();
        jLabel4 = new javax.swing.JLabel();
        tfD = new javax.swing.JTextField();
        tfIteraciones = new javax.swing.JTextField();
        menuBar = new javax.swing.JMenuBar();
        javax.swing.JMenu fileMenu = new javax.swing.JMenu();
        miAbrir = new javax.swing.JMenuItem();
        javax.swing.JMenuItem miSalir = new javax.swing.JMenuItem();
        javax.swing.JMenu helpMenu = new javax.swing.JMenu();
        javax.swing.JMenuItem aboutMenuItem = new javax.swing.JMenuItem();
        statusPanel = new javax.swing.JPanel();
        javax.swing.JSeparator statusPanelSeparator = new javax.swing.JSeparator();
        statusMessageLabel = new javax.swing.JLabel();
        statusAnimationLabel = new javax.swing.JLabel();
        progressBar = new javax.swing.JProgressBar();

        mainPanel.setName("mainPanel"); // NOI18N

        tpPanelP.setName("tpPanelP"); // NOI18N

        pTexto.setName("pTexto"); // NOI18N

        org.jdesktop.application.ResourceMap resourceMap = org.jdesktop.application.Application.getInstance(com.sira.textrankresume.gui.TextRankResumeApp.class).getContext().getResourceMap(TextRankResumeView.class);
        jLabel1.setText(resourceMap.getString("jLabel1.text")); // NOI18N
        jLabel1.setName("jLabel1"); // NOI18N

        btImportar.setText(resourceMap.getString("btImportar.text")); // NOI18N
        btImportar.setName("btImportar"); // NOI18N
        btImportar.addActionListener(new java.awt.event.ActionListener() {
            public void actionPerformed(java.awt.event.ActionEvent evt) {
                btImportarActionPerformed(evt);
            }
        });

        cbResaltarPalabFiltr.setText(resourceMap.getString("cbResaltarPalabFiltr.text")); // NOI18N
        cbResaltarPalabFiltr.setName("cbResaltarPalabFiltr"); // NOI18N
        cbResaltarPalabFiltr.addActionListener(new java.awt.event.ActionListener() {
            public void actionPerformed(java.awt.event.ActionEvent evt) {
                cbResaltarPalabFiltrActionPerformed(evt);
            }
        });

        jScrollPane1.setName("jScrollPane1"); // NOI18N

        tpTexto.setName("tpTexto"); // NOI18N
        jScrollPane1.setViewportView(tpTexto);

        javax.swing.GroupLayout pTextoLayout = new javax.swing.GroupLayout(pTexto);
        pTexto.setLayout(pTextoLayout);
        pTextoLayout.setHorizontalGroup(
            pTextoLayout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
            .addGroup(pTextoLayout.createSequentialGroup()
                .addContainerGap()
                .addGroup(pTextoLayout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
                    .addGroup(pTextoLayout.createSequentialGroup()
                        .addComponent(jLabel1)
                        .addGap(554, 554, 554))
                    .addGroup(javax.swing.GroupLayout.Alignment.TRAILING, pTextoLayout.createSequentialGroup()
                        .addComponent(jScrollPane1, javax.swing.GroupLayout.DEFAULT_SIZE, 480, Short.MAX_VALUE)
                        .addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.UNRELATED)
                        .addGroup(pTextoLayout.createParallelGroup(javax.swing.GroupLayout.Alignment.TRAILING)
                            .addComponent(btImportar, javax.swing.GroupLayout.PREFERRED_SIZE, 149, javax.swing.GroupLayout.PREFERRED_SIZE)
                            .addComponent(cbResaltarPalabFiltr))
                        .addContainerGap())))
        );
        pTextoLayout.setVerticalGroup(
            pTextoLayout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
            .addGroup(pTextoLayout.createSequentialGroup()
                .addContainerGap()
                .addComponent(jLabel1)
                .addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED)
                .addGroup(pTextoLayout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
                    .addGroup(pTextoLayout.createSequentialGroup()
                        .addComponent(btImportar)
                        .addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.UNRELATED)
                        .addComponent(cbResaltarPalabFiltr))
                    .addComponent(jScrollPane1, javax.swing.GroupLayout.DEFAULT_SIZE, 363, Short.MAX_VALUE))
                .addContainerGap())
        );

        tpPanelP.addTab(resourceMap.getString("pTexto.TabConstraints.tabTitle"), pTexto); // NOI18N

        pFiltros.setName("pFiltros"); // NOI18N

        jLabel5.setText(resourceMap.getString("jLabel5.text")); // NOI18N
        jLabel5.setName("jLabel5"); // NOI18N

        jScrollPane3.setName("jScrollPane3"); // NOI18N

        tableFiltros.setModel(new javax.swing.table.DefaultTableModel(
            new Object [][] {

            },
            new String [] {
                "Palabra"
            }
        ) {
            Class[] types = new Class [] {
                java.lang.String.class
            };
            boolean[] canEdit = new boolean [] {
                false
            };

            public Class getColumnClass(int columnIndex) {
                return types [columnIndex];
            }

            public boolean isCellEditable(int rowIndex, int columnIndex) {
                return canEdit [columnIndex];
            }
        });
        tableFiltros.setName("tableFiltros"); // NOI18N
        jScrollPane3.setViewportView(tableFiltros);

        btImportarF.setText(resourceMap.getString("btImportarF.text")); // NOI18N
        btImportarF.setName("btImportarF"); // NOI18N
        btImportarF.addActionListener(new java.awt.event.ActionListener() {
            public void actionPerformed(java.awt.event.ActionEvent evt) {
                btImportarFActionPerformed(evt);
            }
        });

        javax.swing.GroupLayout pFiltrosLayout = new javax.swing.GroupLayout(pFiltros);
        pFiltros.setLayout(pFiltrosLayout);
        pFiltrosLayout.setHorizontalGroup(
            pFiltrosLayout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
            .addGroup(pFiltrosLayout.createSequentialGroup()
                .addContainerGap()
                .addGroup(pFiltrosLayout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
                    .addGroup(javax.swing.GroupLayout.Alignment.TRAILING, pFiltrosLayout.createSequentialGroup()
                        .addComponent(jScrollPane3, javax.swing.GroupLayout.DEFAULT_SIZE, 554, Short.MAX_VALUE)
                        .addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.UNRELATED)
                        .addComponent(btImportarF))
                    .addComponent(jLabel5))
                .addContainerGap())
        );
        pFiltrosLayout.setVerticalGroup(
            pFiltrosLayout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
            .addGroup(pFiltrosLayout.createSequentialGroup()
                .addContainerGap()
                .addComponent(jLabel5)
                .addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED)
                .addGroup(pFiltrosLayout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
                    .addComponent(btImportarF)
                    .addComponent(jScrollPane3, javax.swing.GroupLayout.DEFAULT_SIZE, 363, Short.MAX_VALUE))
                .addContainerGap())
        );

        tpPanelP.addTab(resourceMap.getString("pFiltros.TabConstraints.tabTitle"), pFiltros); // NOI18N

        pResultado.setName("R"); // NOI18N

        jLabel2.setText(resourceMap.getString("jLabel2.text")); // NOI18N
        jLabel2.setName("jLabel2"); // NOI18N

        jScrollPane2.setName("jScrollPane2"); // NOI18N

        tableResultados.setModel(new javax.swing.table.DefaultTableModel(
            new Object [][] {

            },
            new String [] {
                "Sentencia", "Puntuación"
            }
        ) {
            Class[] types = new Class [] {
                java.lang.String.class, java.lang.String.class
            };
            boolean[] canEdit = new boolean [] {
                false, false
            };

            public Class getColumnClass(int columnIndex) {
                return types [columnIndex];
            }

            public boolean isCellEditable(int rowIndex, int columnIndex) {
                return canEdit [columnIndex];
            }
        });
        tableResultados.setName("tableResultados"); // NOI18N
        jScrollPane2.setViewportView(tableResultados);

        btMostrar.setText(resourceMap.getString("btMostrar.text")); // NOI18N
        btMostrar.setEnabled(false);
        btMostrar.setName("btMostrar"); // NOI18N
        btMostrar.addActionListener(new java.awt.event.ActionListener() {
            public void actionPerformed(java.awt.event.ActionEvent evt) {
                btMostrarActionPerformed(evt);
            }
        });

        javax.swing.GroupLayout pResultadoLayout = new javax.swing.GroupLayout(pResultado);
        pResultado.setLayout(pResultadoLayout);
        pResultadoLayout.setHorizontalGroup(
            pResultadoLayout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
            .addGroup(pResultadoLayout.createSequentialGroup()
                .addContainerGap()
                .addGroup(pResultadoLayout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
                    .addGroup(javax.swing.GroupLayout.Alignment.TRAILING, pResultadoLayout.createSequentialGroup()
                        .addComponent(jScrollPane2, javax.swing.GroupLayout.DEFAULT_SIZE, 534, Short.MAX_VALUE)
                        .addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED)
                        .addComponent(btMostrar))
                    .addComponent(jLabel2))
                .addContainerGap())
        );
        pResultadoLayout.setVerticalGroup(
            pResultadoLayout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
            .addGroup(pResultadoLayout.createSequentialGroup()
                .addContainerGap()
                .addComponent(jLabel2)
                .addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED)
                .addGroup(pResultadoLayout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
                    .addComponent(btMostrar)
                    .addComponent(jScrollPane2, javax.swing.GroupLayout.DEFAULT_SIZE, 363, Short.MAX_VALUE))
                .addContainerGap())
        );

        tpPanelP.addTab(resourceMap.getString("R.TabConstraints.tabTitle"), pResultado); // NOI18N

        btTratar.setText(resourceMap.getString("btTratar.text")); // NOI18N
        btTratar.setName("btTratar"); // NOI18N
        btTratar.addActionListener(new java.awt.event.ActionListener() {
            public void actionPerformed(java.awt.event.ActionEvent evt) {
                btTratarActionPerformed(evt);
            }
        });

        jLabel3.setText(resourceMap.getString("jLabel3.text")); // NOI18N
        jLabel3.setName("jLabel3"); // NOI18N

        cbFiltro.setText(resourceMap.getString("cbFiltro.text")); // NOI18N
        cbFiltro.setName("cbFiltro"); // NOI18N

        jLabel4.setText(resourceMap.getString("jLabel4.text")); // NOI18N
        jLabel4.setName("jLabel4"); // NOI18N

        tfD.setHorizontalAlignment(javax.swing.JTextField.RIGHT);
        tfD.setText(Float.toString(0.85f));
        tfD.setMaximumSize(new java.awt.Dimension(90, 20));
        tfD.setMinimumSize(new java.awt.Dimension(90, 20));
        tfD.setName("tfD"); // NOI18N
        tfD.setPreferredSize(new java.awt.Dimension(90, 20));

        tfIteraciones.setHorizontalAlignment(javax.swing.JTextField.RIGHT);
        tfIteraciones.setText(Integer.toString(20));
        tfIteraciones.setMaximumSize(new java.awt.Dimension(90, 20));
        tfIteraciones.setMinimumSize(new java.awt.Dimension(90, 20));
        tfIteraciones.setName("tfIteraciones"); // NOI18N
        tfIteraciones.setPreferredSize(new java.awt.Dimension(90, 20));

        javax.swing.GroupLayout mainPanelLayout = new javax.swing.GroupLayout(mainPanel);
        mainPanel.setLayout(mainPanelLayout);
        mainPanelLayout.setHorizontalGroup(
            mainPanelLayout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
            .addGroup(mainPanelLayout.createSequentialGroup()
                .addContainerGap()
                .addGroup(mainPanelLayout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
                    .addComponent(tpPanelP, javax.swing.GroupLayout.DEFAULT_SIZE, 664, Short.MAX_VALUE)
                    .addGroup(mainPanelLayout.createSequentialGroup()
                        .addComponent(btTratar, javax.swing.GroupLayout.PREFERRED_SIZE, 149, javax.swing.GroupLayout.PREFERRED_SIZE)
                        .addGap(40, 40, 40)
                        .addComponent(jLabel3, javax.swing.GroupLayout.PREFERRED_SIZE, 19, javax.swing.GroupLayout.PREFERRED_SIZE)
                        .addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED)
                        .addComponent(tfD, javax.swing.GroupLayout.PREFERRED_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.PREFERRED_SIZE)
                        .addGap(88, 88, 88)
                        .addComponent(jLabel4)
                        .addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED)
                        .addComponent(tfIteraciones, javax.swing.GroupLayout.PREFERRED_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.PREFERRED_SIZE)
                        .addGap(37, 37, 37)
                        .addComponent(cbFiltro, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE)))
                .addContainerGap())
        );
        mainPanelLayout.setVerticalGroup(
            mainPanelLayout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
            .addGroup(javax.swing.GroupLayout.Alignment.TRAILING, mainPanelLayout.createSequentialGroup()
                .addContainerGap()
                .addComponent(tpPanelP, javax.swing.GroupLayout.DEFAULT_SIZE, 433, Short.MAX_VALUE)
                .addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED)
                .addGroup(mainPanelLayout.createParallelGroup(javax.swing.GroupLayout.Alignment.BASELINE)
                    .addComponent(btTratar)
                    .addComponent(jLabel3)
                    .addComponent(cbFiltro, javax.swing.GroupLayout.PREFERRED_SIZE, 23, javax.swing.GroupLayout.PREFERRED_SIZE)
                    .addComponent(jLabel4)
                    .addComponent(tfD, javax.swing.GroupLayout.PREFERRED_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.PREFERRED_SIZE)
                    .addComponent(tfIteraciones, javax.swing.GroupLayout.PREFERRED_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.PREFERRED_SIZE))
                .addGap(16, 16, 16))
        );

        menuBar.setName("menuBar"); // NOI18N

        fileMenu.setText(resourceMap.getString("fileMenu.text")); // NOI18N
        fileMenu.setName("fileMenu"); // NOI18N

        miAbrir.setText(resourceMap.getString("miAbrir.text")); // NOI18N
        miAbrir.setName("miAbrir"); // NOI18N
        miAbrir.addActionListener(new java.awt.event.ActionListener() {
            public void actionPerformed(java.awt.event.ActionEvent evt) {
                miAbrirActionPerformed(evt);
            }
        });
        fileMenu.add(miAbrir);

        javax.swing.ActionMap actionMap = org.jdesktop.application.Application.getInstance(com.sira.textrankresume.gui.TextRankResumeApp.class).getContext().getActionMap(TextRankResumeView.class, this);
        miSalir.setAction(actionMap.get("quit")); // NOI18N
        miSalir.setText(resourceMap.getString("miSalir.text")); // NOI18N
        miSalir.setName("miSalir"); // NOI18N
        fileMenu.add(miSalir);

        menuBar.add(fileMenu);

        helpMenu.setText(resourceMap.getString("helpMenu.text")); // NOI18N
        helpMenu.setName("helpMenu"); // NOI18N

        aboutMenuItem.setAction(actionMap.get("showAboutBox")); // NOI18N
        aboutMenuItem.setName("aboutMenuItem"); // NOI18N
        helpMenu.add(aboutMenuItem);

        menuBar.add(helpMenu);

        statusPanel.setName("statusPanel"); // NOI18N

        statusPanelSeparator.setName("statusPanelSeparator"); // NOI18N

        statusMessageLabel.setName("statusMessageLabel"); // NOI18N

        statusAnimationLabel.setHorizontalAlignment(javax.swing.SwingConstants.LEFT);
        statusAnimationLabel.setName("statusAnimationLabel"); // NOI18N

        progressBar.setName("progressBar"); // NOI18N

        javax.swing.GroupLayout statusPanelLayout = new javax.swing.GroupLayout(statusPanel);
        statusPanel.setLayout(statusPanelLayout);
        statusPanelLayout.setHorizontalGroup(
            statusPanelLayout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
            .addComponent(statusPanelSeparator, javax.swing.GroupLayout.DEFAULT_SIZE, 684, Short.MAX_VALUE)
            .addGroup(statusPanelLayout.createSequentialGroup()
                .addContainerGap()
                .addComponent(statusMessageLabel)
                .addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED, 514, Short.MAX_VALUE)
                .addComponent(progressBar, javax.swing.GroupLayout.PREFERRED_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.PREFERRED_SIZE)
                .addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED)
                .addComponent(statusAnimationLabel)
                .addContainerGap())
        );
        statusPanelLayout.setVerticalGroup(
            statusPanelLayout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
            .addGroup(statusPanelLayout.createSequentialGroup()
                .addComponent(statusPanelSeparator, javax.swing.GroupLayout.PREFERRED_SIZE, 2, javax.swing.GroupLayout.PREFERRED_SIZE)
                .addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED, javax.swing.GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE)
                .addGroup(statusPanelLayout.createParallelGroup(javax.swing.GroupLayout.Alignment.BASELINE)
                    .addComponent(statusMessageLabel)
                    .addComponent(statusAnimationLabel)
                    .addComponent(progressBar, javax.swing.GroupLayout.PREFERRED_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.PREFERRED_SIZE))
                .addGap(3, 3, 3))
        );

        setComponent(mainPanel);
        setMenuBar(menuBar);
        setStatusBar(statusPanel);
    }// </editor-fold>//GEN-END:initComponents

    private void miAbrirActionPerformed(java.awt.event.ActionEvent evt) {//GEN-FIRST:event_miAbrirActionPerformed
        abrirFichero();
    }//GEN-LAST:event_miAbrirActionPerformed

    private void btImportarActionPerformed(java.awt.event.ActionEvent evt) {//GEN-FIRST:event_btImportarActionPerformed
        abrirFichero();
    }//GEN-LAST:event_btImportarActionPerformed

    private void btImportarFActionPerformed(java.awt.event.ActionEvent evt) {//GEN-FIRST:event_btImportarFActionPerformed
        importarF();
    }//GEN-LAST:event_btImportarFActionPerformed

    private void btTratarActionPerformed(java.awt.event.ActionEvent evt) {//GEN-FIRST:event_btTratarActionPerformed
        ejecutarAlgoritmo();
    }//GEN-LAST:event_btTratarActionPerformed

    private void btMostrarActionPerformed(java.awt.event.ActionEvent evt) {//GEN-FIRST:event_btMostrarActionPerformed
        //JDialog dialog = new GraphDialog(this.getFrame(), true, tarea.getGrafo());
        //dialog.setVisible(true);

        //JFrame f = new GraphFrame(tarea.getGrafo());
        //f.setVisible(true);
        GraphJDialog dialog = new GraphJDialog(this.getFrame(), true, tarea.getGrafo());
        dialog.setVisible(true);
    }//GEN-LAST:event_btMostrarActionPerformed

    private void cbResaltarPalabFiltrActionPerformed(java.awt.event.ActionEvent evt) {//GEN-FIRST:event_cbResaltarPalabFiltrActionPerformed
        resaltarPalabrasFiltradas(cbResaltarPalabFiltr.isSelected());
    }//GEN-LAST:event_cbResaltarPalabFiltrActionPerformed

    // Variables declaration - do not modify//GEN-BEGIN:variables
    private javax.swing.JButton btImportar;
    private javax.swing.JButton btImportarF;
    private javax.swing.JButton btMostrar;
    private javax.swing.JButton btTratar;
    private javax.swing.JCheckBox cbFiltro;
    private javax.swing.JCheckBox cbResaltarPalabFiltr;
    private javax.swing.JLabel jLabel1;
    private javax.swing.JLabel jLabel2;
    private javax.swing.JLabel jLabel3;
    private javax.swing.JLabel jLabel4;
    private javax.swing.JLabel jLabel5;
    private javax.swing.JScrollPane jScrollPane1;
    private javax.swing.JScrollPane jScrollPane2;
    private javax.swing.JScrollPane jScrollPane3;
    private javax.swing.JPanel mainPanel;
    private javax.swing.JMenuBar menuBar;
    private javax.swing.JMenuItem miAbrir;
    private javax.swing.JPanel pFiltros;
    private javax.swing.JPanel pResultado;
    private javax.swing.JPanel pTexto;
    private javax.swing.JProgressBar progressBar;
    private javax.swing.JLabel statusAnimationLabel;
    private javax.swing.JLabel statusMessageLabel;
    private javax.swing.JPanel statusPanel;
    private javax.swing.JTable tableFiltros;
    private javax.swing.JTable tableResultados;
    private javax.swing.JTextField tfD;
    private javax.swing.JTextField tfIteraciones;
    private javax.swing.JTabbedPane tpPanelP;
    private javax.swing.JTextPane tpTexto;
    // End of variables declaration//GEN-END:variables
    private final Timer messageTimer;
    private final Timer busyIconTimer;
    private final Icon idleIcon;
    private final Icon[] busyIcons = new Icon[15];
    private int busyIconIndex = 0;
    private JDialog aboutBox;

    /* ATRIBUTOS PRIVADOS ESPECÍFICOS */
    private List<String> filtro = new ArrayList<String>();
    private TaskTextRankResume tarea;
    private SimpleAttributeSet estiloPorDefecto;
    private SimpleAttributeSet estiloResaltado;


    /* FUNCIONES PRIVADAS ESPECÍFICAS */
    /**
     * Ejecuta las tareas pasadas como argumentos.
     * 
     * @param t tarea a ejecutar
     */
    private void ejecutar(Task t) {
        this.getApplication().getContext().getTaskService().execute(t);
    }

    private void ejecutarAlgoritmo() {
        if (tpTexto.getText().length() > 0) {
            borraTabla(tableResultados);
            int iteraciones = Integer.parseInt(tfIteraciones.getText());
            float d = Float.parseFloat(tfD.getText());
            Filtro f;

            if (cbFiltro.isSelected() && filtro != null) {
                f = new Filtro(filtro);
            } else {
                f = new Filtro(new LinkedList<String>());
            }

            //Creamos la tarea
            tarea = new TaskTextRankResume(this.getApplication(),
                    tpTexto.getText(),
                    f,
                    d,
                    iteraciones);

            //La ejecutamos
            ejecutar(tarea);

            //Activamos el botón de mostrar grafo
            btMostrar.setEnabled(true);
            //Mostramos la pestaña de resultados.
            tpPanelP.setSelectedComponent(pResultado);
        } else {
           JOptionPane.showMessageDialog( this.getFrame(),
            "Es necesario un texto a tratar.","Error",
                JOptionPane.WARNING_MESSAGE );
           tpPanelP.setSelectedComponent(pTexto);
        }
    }

    private void mostrarResultados(List<Sentencia> lista) {
        DefaultTableModel model = (DefaultTableModel) tableResultados.getModel();
        Iterator<Sentencia> it = lista.iterator();
        while (it.hasNext()) {
            Sentencia aux = it.next();
            model.addRow(new String[]{aux.getTexto(), Float.toString(aux.getPuntuacion())});
        }
    }

    private void cargarTexto(String texto) {
        tpTexto.setText(texto);
        btTratar.setEnabled(true);
    }

    private void abrirFichero() {
        JFileChooser jFile = new JFileChooser();
        jFile.setDialogType(JFileChooser.OPEN_DIALOG);
        jFile.setMultiSelectionEnabled(false);

        if (jFile.showDialog(this.getComponent(), "Abrir fichero") == JFileChooser.APPROVE_OPTION) {
            String texto = "";
            try {
                FileReader fr = new FileReader(jFile.getSelectedFile());
                BufferedReader br = new BufferedReader(fr);

                StringBuffer sb = new StringBuffer();
                String cadena;

                while ((cadena = br.readLine()) != null) {
                    sb.append(cadena);
                    sb.append("\n");
                }

                texto = sb.toString();

                cargarTexto(texto);
            } catch (FileNotFoundException ex) {
                Logger.getLogger(TextRankResumeView.class.getName()).log(Level.SEVERE, null, ex);
            } catch (IOException ex) {
                Logger.getLogger(TextRankResumeView.class.getName()).log(Level.SEVERE, null, ex);
            }
        }
    }

    /* FUNCIONES DE FILTRO: */
    private void importarF() {
        filtro.clear();
        importarFiltros();
        borraTabla(tableFiltros);
        actualizarTabla(filtro);
        //Nos movemos a la pestaña de los filtros
        tpPanelP.setSelectedComponent(pFiltros);
        cbFiltro.setSelected(true);
    }

    private void borraTabla(JTable tabla) {
        DefaultTableModel dtm = (DefaultTableModel) tabla.getModel();
        String nombres[] = new String[dtm.getColumnCount()];

        for (int i = 0; i < nombres.length; i++) {
            nombres[i] = dtm.getColumnName(i);
        }

        tabla.setModel(new DefaultTableModel(nombres, 0));

    }

    private void actualizarTabla(List<String> lista) {

        Iterator<String> it = lista.iterator();
        while (it.hasNext()) {
            addPalabraTabla(it.next());
        }
    }

    private void addPalabraTabla(String palabra) {
        DefaultTableModel model = (DefaultTableModel) tableFiltros.getModel();
        model.addRow(new String[]{palabra});
    }

    private void importarFiltros() {
        JFileChooser fileChooser = new JFileChooser();
        fileChooser.setDialogType(JFileChooser.OPEN_DIALOG);
        if (fileChooser.showDialog(this.getComponent(), "Importar") == JFileChooser.APPROVE_OPTION) {
            FileReader fr = null;
            try {
                fr = new FileReader(fileChooser.getSelectedFile());
                BufferedReader br = new BufferedReader(fr);
                String cadena;

                while ((cadena = br.readLine()) != null) {
                    if (cadena.length() > 0) {
                        filtro.add(cadena);
                    }
                }
            } catch (FileNotFoundException ex2) {
                Logger.getLogger(TextRankResumeView.class.getName()).log(Level.SEVERE, null, ex2);
            } catch (IOException ex) {
                Logger.getLogger(TextRankResumeView.class.getName()).log(Level.SEVERE, null, ex);
            } finally {
                try {
                    fr.close();
                } catch (IOException ex) {
                    Logger.getLogger(TextRankResumeView.class.getName()).log(Level.SEVERE, null, ex);
                }
            }
        }
    }

    private void resaltarPalabrasFiltradas(boolean res) {
        ModificadorFuente mf = ModificadorFuente.getInstance();

        if (res) {
            mf.modificarEstiloPalabrasEncontradas(tpTexto.getText(),
                    filtro,
                    estiloResaltado,
                    tpTexto.getStyledDocument());
        } else {
            tpTexto.getStyledDocument().setCharacterAttributes(0,
                    tpTexto.getStyledDocument().getLength(),
                    estiloPorDefecto,
                    true);
        }
    }

    class TaskTextRankResume extends Task {

        private String texto;
        private IFiltro filtro;
        private float d;
        private int it;
        private ITextRankResume textrank;

        public TaskTextRankResume(Application application, String texto, IFiltro filtro, float d, int it) {
            super(application);

            this.texto = texto;
            this.filtro = filtro;
            this.d = d;
            this.it = it;

            textrank = new TextRankResume(texto, filtro);
        }

        @Override
        protected synchronized Object doInBackground() throws Exception {
            String text;
            if (texto.length() > 15) {
                text = texto.substring(0, 15);
            } else {
                text = texto;
            }

            System.out.println("Lanzando algoritmo: texto " + text + "..., d: " + d + ", it: " + it + ", filtro: " + filtro.getPalabrasANoTenerEnCuenta().size() + " palabras.");
            setProgress(0.1f);
            setMessage("Creando grafo");
            textrank.crearGrafo(d, it);
            setProgress(0.9f);
            setMessage("Algoritmo TextRank finalizado");
            mostrarResultados(textrank.getResumenes());
            setProgress(1.0f);
            return true;
        }

        public List<Sentencia> getSentencias() {
            return textrank.getResumenes();
        }

        public Grafo getGrafo() {
            return textrank.getGrafo();
        }
    }
}
